package Server;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.net.Socket;
import java.util.ArrayList;
import java.util.Scanner;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.JTextArea;

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
/**
 *
 * @author Rosie
 */
public class serverchat implements Runnable {

    private Socket socket;
    BufferedReader buffRead = null;
    BufferedWriter buffWrite = null;
    String message = "";
    JTextArea usersOnlineTA;
    ArrayList clients;
    ArrayList clientList;
    BufferedWriter out;

    serverchat(Socket s, JTextArea u, ArrayList c, ArrayList clientsList) {
        socket = s;
        usersOnlineTA = u;
        clients = c;
        clientList = clientsList;
        try {
            buffRead = new BufferedReader(new InputStreamReader(socket.getInputStream()));
            buffWrite = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));
            Thread th = new Thread(this);
            th.start();
        } catch (IOException e) {
            System.exit(-1);
        }
    }

    @Override
    public void run() {
        String uname = "";
        String fileName = "";
        while (true) {
            try {
                message = buffRead.readLine();
                System.out.println("Message from Client: "+message);
                if (message.startsWith("username")) {
                    String user = message.substring(10, message.length());
                    if (clients.contains(user)) {
                        sendTo("invalidXUserXNameX32X12");
                    } else {
                        sendTo("validXUserXNameX32X11");
                        clients.add(user);
                        usersOnlineTA.append(user + "\n");
                        message = "newClientsList,";
                        int i = 0;
                        for (i = 0; i < clients.size() - 1; i++) {
                            message += clients.get(i) + ",";
                        }
                        if (!clients.isEmpty()) {
                            message += clients.get(i);
                            System.out.println(message);
                            for (i = 0; i < clients.size(); i++) {
                                ((serverchat) clientList.get(i)).sendTo(message);
                            }
                        }
                    }
                } else if (message.startsWith("disXXX")) {
                    String user = message.substring(7, message.length());
                    clients.remove(user);
                    usersOnlineTA.setText("");
                    for (int i = 0; i < clients.size(); i++) {
                        usersOnlineTA.append(clients.get(i).toString() + "\n");
                    }

                    // send new List of clients to connected clients
                    message = "newClientsList,";
                    int i = 0;
                    for (i = 0; i < clients.size() - 1; i++) {
                        message += clients.get(i) + ",";
                    }

                    if (!clients.isEmpty()) {
                        message += clients.get(i);
                        for (i = 0; i < clients.size(); i++) {
                            ((serverchat) clientList.get(i)).sendTo(message);
                        }
                    }

                } else if (message.startsWith("fromXtoX")) {
                    message = message.substring(9, message.length());   // remove "fromXtoX" from message
                    String[] chatDetails = message.split(":");
                    String from = chatDetails[0];
                    String to = chatDetails[1];
                    message = "sent " + from + ":" + to + ":" + chatDetails[2];

                    if (chatDetails.length > 2) {
                        int i;
                        for (i = 3; i < chatDetails.length - 1; i++) {
                            message += chatDetails[i] + ":";
                        }
                        message += chatDetails[i];
                    }

                    if (!to.startsWith("GROUPXX1X01")) {
                        for (int i = 0; i < clients.size(); i++) {
                            if (to.equals(clients.get(i).toString())) {
                                ((serverchat) clientList.get(i)).sendTo(message);
                                break;
                            }
                        }
                    } else {
                        String groupName = to.substring(12, to.length());
                        if (groupName.equals("EVERYONE")) {
                            for (int i = 0; i < clients.size(); i++) {
                                if (!clients.get(i).equals(from)) {
                                    ((serverchat) clientList.get(i)).sendTo(message);
                                }
                            }
                        } else {
                            String[] users = message.split(":");
                            String[] toUsers = users[2].split(",");
                            for (int i = 0; i < toUsers.length; i++) {
                                System.out.print(toUsers[i] + ", ");
                            }

                            for (int i = 0; i < toUsers.length - 1; i++) {
                                if (clients.contains(toUsers[i])) {
                                    ((serverchat) clientList.get(clients.indexOf(toUsers[i]))).sendTo(message);
                                }
                            }
                        }
                    }

                } else if (message.startsWith("newGroupMembers")) {
                    String gMembers = message.substring(16, message.length());
                    String[] members = gMembers.split(":");
                    for (int i = 1; i < members.length; i++) {
                        if (clients.contains(members[i])) {
                            ((serverchat) clientList.get(clients.indexOf(members[i]))).sendTo(message);
                        }
                    }
                } else if (message.startsWith("isFile")) {
                    message = message.substring(7, message.length());
                    System.out.println(message);
                    if (message.startsWith("EOFXXX9999X0123")) {
                        out.close();
                        System.out.println("file received "+fileName);

                        String[] members = message.split(":");

                        if (members[1].equals("EVERYONE")) {
                            System.out.println("file is sent to EVERYONE");
                            message = "fileSent:EVERYONE:" + uname + "_" + fileName;
                            for (int i = 0; i < clients.size(); i++) {
                                ((serverchat) clientList.get(i)).sendTo(message);
                            }
                        } else if(members[1].equals("GROUPXX1X01")) {
                            System.out.println("file is sent to "+members[2]);
                            message = "fileSent:GROUPXX1X01:"+members[2]+":"+ uname + "_" + fileName;
                            System.out.println(message);
                            for (int i = 3; i < members.length; i++) {
                                if (clients.contains(members[i])) {
                                    System.out.println("- File sent to " + members[i]);
                                    System.out.println("- Message: " + message);
                                    ((serverchat) clientList.get(clients.indexOf(members[i]))).sendTo(message);
                                } else{
                                    System.out.println("! File not sent to " + members[i]);
                                }
                            }
                        } else{
                            message = "fileSent:X:" + uname + "_" + fileName;
                            ((serverchat) clientList.get(clients.indexOf(members[1]))).sendTo(message);
                        }
                    } else if (message.startsWith("startFileBufferXXX9999X0123")) {
                        System.out.println("directory: " + message);
                        String[] t = message.split(" ");
                        uname = t[1];
                        fileName = "";
                        int i;
                        for (i = 2; i < t.length - 1; i++) {
                            fileName += t[i];
                            fileName += " ";
                        }
                        fileName += t[i];
                        System.out.println(".... " + "/temp/" + uname + "/" + fileName);
                        out = new BufferedWriter(new FileWriter("temp/" + uname + "_" + fileName));
                    } else {
                        out.append(message + System.getProperty("line.separator"));
                    }
                } else if(message.startsWith("Download:")){
                    String temp = message.substring(10, message.length());
                    String[] details = temp.split(":");
                    String sender = details[1];
                    File file = new File("temp/"+details[0]);
                    System.out.println(sender +" requests file: "+file.getName());
                    Scanner s = new Scanner(file);
                    String tmp = "";

                    ((serverchat)clientList.get(clients.indexOf(sender))).sendTo("RecieveFileXXKJKStart:"+file.getName());
                    while(s.hasNextLine()){
                        tmp = s.nextLine();
                        ((serverchat)clientList.get(clients.indexOf(sender))).sendTo("RecieveFileXXKJK "+tmp);
                    }
                    ((serverchat)clientList.get(clients.indexOf(sender))).sendTo("RecieveFileXXKJKEnd");
                }
            } catch (IOException e) {
            }
        }
    }

    public void sendTo(String message) {
        try {
            this.buffWrite.write(message);
            this.buffWrite.newLine();
            this.buffWrite.flush();
        } catch (IOException ex) {
            Logger.getLogger(serverchat.class.getName()).log(Level.SEVERE, null, ex);
        }
    }

    void disconnect() {
        for (int i = 0; i < clients.size(); i++) {
            ((serverchat) clientList.get(i)).sendTo("serverDown");
        }
    }
}
